/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package pe.com.cotelasa.scp.controlador;

import java.io.FileOutputStream;
import java.io.IOException;
import java.io.Serializable;
import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.List;
import java.util.Map;
import javax.faces.context.ExternalContext;
import javax.faces.context.FacesContext;
import javax.inject.Inject;
import javax.inject.Named;
import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFDataFormat;
import org.apache.poi.hssf.usermodel.HSSFFont;
import org.apache.poi.hssf.usermodel.HSSFPalette;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.hssf.util.HSSFColor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import pe.com.cotelasa.common.controlador.MBGenerico;
import pe.com.cotelasa.scp.common.IObserver;
import pe.com.cotelasa.scp.controlador.backingBean.BKArticuloStock;
import pe.com.cotelasa.scp.dominio.common.Constantes;
import pe.com.cotelasa.scp.dominio.common.URLPaginacion;
import pe.com.cotelasa.scp.dominio.common.util.UtilitarioFecha;
import pe.com.cotelasa.scp.dominio.excepcion.ServiceException;
import pe.com.cotelasa.scp.dominio.service.IServicioArticulo;
import pe.com.cotelasa.scp.dominio.service.IServicioArticuloSede;
import pe.com.cotelasa.scp.dominio.service.IServicioCategoriaArticulo;
import pe.com.cotelasa.scp.dominio.service.IServicioCierreInventario;
import pe.com.cotelasa.scp.dominio.service.IServicioTipoCambio;
import pe.com.cotelasa.scp.entidad.Articulo;
import pe.com.cotelasa.scp.entidad.ArticuloSede;
import pe.com.cotelasa.scp.entidad.CategoriaArticulo;
import pe.com.cotelasa.scp.entidad.CierreInventario;
import pe.com.cotelasa.scp.entidad.Sede;
import pe.com.cotelasa.scp.entidad.TipoCambio;
import pe.com.cotelasa.seguridad.controlador.backingBean.BKSession;

/**
 *
 * @author WINDOWS 7
 */
@Named(value = "MBArticuloStock")
@Scope("request")
public class MBArticuloStock extends MBGenerico implements IObserver, Serializable {

    @Inject
    private BKArticuloStock bk;
    @Inject
    private IServicioArticuloSede servicio;
    @Inject
    private IServicioCategoriaArticulo servicioCategoria;
    @Inject
    private IServicioArticulo servicioArticulo;
    @Inject
    private IServicioCierreInventario servicioCierre;
    @Inject
    private IServicioTipoCambio servicioTipoCambio;
    @Inject
    private IServicioCierreInventario servicioCierreInventario;
    @Inject
    private MBCompBuscarDireccion mbSede;
    @Autowired
    BKSession session;

    public void buscarStockArticulo() {

        try {
            if (bk.getArticuloBusqueda().getSede().getDireccion().equalsIgnoreCase("")) {
                bk.getArticuloBusqueda().setSede(null);
            }
            bk.setListaArticuloStock(servicio.listaStockPorFiltro(bk.getArticuloBusqueda()));
            bk.getArticuloBusqueda().setSede(new Sede());
            /*for(ArticuloSede art:bk.getListaArticuloStock()){
             if(art.getFecIngreso() != null){
             art.setNumDias(UtilitarioFecha.restarFechas(new Date(), art.getFecIngreso()));
             }
             }*/
        } catch (ServiceException e) {
            e.printStackTrace();
        }
    }

    public String mostrarMantenimiento() {
        mbSede.addObserver(this);
        bk.setListaArticuloStock(null);
        bk.setArticuloBusqueda(new ArticuloSede());
        bk.getArticuloBusqueda().setArticulo(new Articulo());
        bk.getArticuloBusqueda().setEmpresa(session.getEmpresa());
        bk.getArticuloBusqueda().setSede(new Sede());
        bk.getArticuloBusqueda().setCodigoCliente("");
        try {

            bk.setListaSubCategoriaEcontrada(servicioCategoria.listarCategoriasArticulosActivos());

        } catch (ServiceException e) {
            e.printStackTrace();
        }

        return URLPaginacion.ArticuloStock.URL_LISTA_ARTICULO_STOCK;
    }

    @Override
    public void actualizarObservador(Object object) {
        Map<String, Object> datos = (Map<String, Object>) object;
        Sede sede = (Sede) datos.get("sede");
        bk.getArticuloBusqueda().setSede(sede);
        //buscarArticulos();
        //bkOrdenCompra.getOrdenCompraFormulario().setLugarEntrega(sede.getDireccion() + " " + (sede.getReferencia() != null ? sede.getReferencia() : ""));
    }

    public void buscarArticulo() {
        try {

            Articulo articulo = new Articulo();
            articulo.setIdCategoriaArticulo(this.bk.getArticuloBusqueda().getArticulo().getIdCategoriaArticulo());
            //this.bk.setListaArticulo(servicioArticulo.listarArticulosPorCategoria(articulo));
            this.bk.setListaModelosDistintos(servicioArticulo.listarModelosDistintos(articulo));
        } catch (ServiceException e) {
            e.printStackTrace();
            mostrarError("Ocurrieron algunos problemas al cargar la informacion. Vuelva a intentar.");
        }
    }
    
    public void buscarArticuloPorModelo() {
        try {

            Articulo articulo = new Articulo();
            articulo.setIdCategoriaArticulo(this.bk.getArticuloBusqueda().getArticulo().getIdCategoriaArticulo());
            articulo.setModelo(this.bk.getArticuloBusqueda().getArticulo().getModelo());
            this.bk.setListaArticulo(servicioArticulo.buscarArticulosPorModelo(articulo));
        } catch (ServiceException e) {
            e.printStackTrace();
            mostrarError("Ocurrieron algunos problemas al cargar la informacion. Vuelva a intentar.");
        }
    }

    public String buscarRazonSocial(Sede sede) {

        if (sede.getIdEmpresa() != null) {
            return sede.getIdEmpresa().getNombreComercial();
        } else if (sede.getIdProveedor() != null) {
            return sede.getIdProveedor().getNombreComercial();
        }
        return "";
    }

    public String mostrarMantenimiento1() {

        try {

            bk.setListaCategoriasOrdenada(servicioCategoria.listarCategoriasPadres());

        } catch (ServiceException e) {
            e.printStackTrace();
        }

        return URLPaginacion.InventarioStock.URL_LISTA_INVENTARIO_STOCK;
    }

    public void cerrarInventario() {
        try {
            SimpleDateFormat sdf = new SimpleDateFormat(Constantes.Fecha.FORMATO_FECHA_ARCHIVO);
            String hoy = sdf.format(new Date());
            String[] fechaVector = hoy.split("-");
            Date fecha = UtilitarioFecha.construirFecha(
                    Integer.parseInt(fechaVector[2]), Integer.parseInt(fechaVector[1]), Integer.parseInt(fechaVector[0]));
            CierreInventario cierre = servicioCierre.conseguirCierreInventarioPorFecha(fecha);
            if (cierre == null) {
                TipoCambio tipoCambio = new TipoCambio();
                tipoCambio.setFecCreacion(new Date());
                bk.setTipoCambio(servicioTipoCambio.ValidarTipoCambio(tipoCambio));
                if (bk.getTipoCambio() != null) {
                    generarReporteInventario(fecha);
                } else {
                    mostrarError("Registre el tipo de cambio de hoy");
                }

            } else {
                mostrarError("Ya existe un cierre con el día de hoy");
            }

        } catch (ServiceException e) {
            e.printStackTrace();
        }
    }

    public void generarReporteInventario(Date fecha) {

        BigDecimal tipoCambio = bk.getTipoCambio().getVenta();

        HSSFWorkbook wb = new HSSFWorkbook();
        HSSFSheet sheet = wb.createSheet("Inventario");

        sheet.setAutobreaks(true);
        sheet.setDefaultColumnWidth(15);
        sheet.setAlternativeFormula(true);
        //sheet.setVerticallyCenter(true);
        sheet.setRowSumsBelow(true);

        HSSFCellStyle borderStyle = wb.createCellStyle();
        borderStyle.setBorderBottom(HSSFCellStyle.BORDER_THIN);
        borderStyle.setBorderLeft(HSSFCellStyle.BORDER_THIN);
        borderStyle.setBorderRight(HSSFCellStyle.BORDER_THIN);
        borderStyle.setBorderTop(HSSFCellStyle.BORDER_THIN);

        HSSFCellStyle borderTBStyle = wb.createCellStyle();
        borderTBStyle.setBorderBottom(HSSFCellStyle.BORDER_THIN);
        borderTBStyle.setBorderTop(HSSFCellStyle.BORDER_THIN);

        HSSFPalette palette = wb.getCustomPalette();
        palette.setColorAtIndex(HSSFColor.GREY_25_PERCENT.index, (byte) 192, (byte) 192, (byte) 192);
        palette.setColorAtIndex(HSSFColor.PLUM.index, (byte) 102, (byte) 102, (byte) 153);
        /**
         * ***** fuente para encabezado ******************
         */
        HSSFFont cabFont = wb.createFont();
        cabFont.setColor(HSSFColor.BLUE.index);
        cabFont.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
        cabFont.setFontHeightInPoints(Short.valueOf("9"));

        HSSFCellStyle cabStyle = wb.createCellStyle();
        cabStyle.setFont(cabFont);

        /**
         * ***** fuente para titulos ******************
         */
        HSSFFont titFont = wb.createFont();
        titFont.setColor(HSSFColor.VIOLET.index);
        titFont.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
        titFont.setFontHeightInPoints(Short.valueOf("7"));

        HSSFCellStyle titStyle = wb.createCellStyle();
        titStyle.cloneStyleFrom(borderStyle);
        titStyle.setFillForegroundColor(HSSFColor.GREY_25_PERCENT.index);
        titStyle.setFillPattern(HSSFCellStyle.SOLID_FOREGROUND);
        titStyle.setFont(titFont);

        /**
         * ***** fuente para negrita normal ******************
         */
        HSSFFont negFont = wb.createFont();
        negFont.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
        negFont.setFontHeightInPoints(Short.valueOf("7"));

        HSSFCellStyle negStyle = wb.createCellStyle();
        negStyle.cloneStyleFrom(borderStyle);
        negStyle.setFont(negFont);


        /**
         * ***** fuente para resultados ******************
         */
        HSSFCellStyle resStyle = wb.createCellStyle();
        resStyle.cloneStyleFrom(borderTBStyle);
        resStyle.setFillForegroundColor(HSSFColor.GREY_25_PERCENT.index);
        resStyle.setFillPattern(HSSFCellStyle.SOLID_FOREGROUND);
        resStyle.setFont(negFont);

        /**
         * ***** fuente para resultados cat ******************
         */
        HSSFFont blaFont = wb.createFont();
        blaFont.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);
        blaFont.setFontHeightInPoints(Short.valueOf("7"));
        blaFont.setColor(HSSFColor.WHITE.index);

        HSSFCellStyle resCStyle = wb.createCellStyle();
        resCStyle.cloneStyleFrom(borderTBStyle);
        resCStyle.setFillForegroundColor(HSSFColor.PLUM.index);
        resCStyle.setFillPattern(HSSFCellStyle.SOLID_FOREGROUND);
        resCStyle.setFont(blaFont);

        /**
         * fuente para normal ***************
         */
        HSSFFont norFont = wb.createFont();
        norFont.setFontHeightInPoints(Short.valueOf("7"));

        HSSFCellStyle norStyle = wb.createCellStyle();
        norStyle.setFont(norFont);

        HSSFCellStyle tcStyle = wb.createCellStyle();
        tcStyle.setFont(norFont);
        tcStyle.setDataFormat(HSSFDataFormat.getBuiltinFormat("0.00"));


        HSSFRow row = sheet.createRow(0);
        HSSFCell cell = row.createCell(0);
        cell.setCellStyle(cabStyle);
        cell.setCellValue(session.getEmpresa().getNombreComercial());

        cell = row.createCell(4);
        cell.setCellStyle(negStyle);
        cell.setCellValue("FECHA");

        cell = row.createCell(5);
        cell.setCellStyle(norStyle);
        cell.setCellValue(UtilitarioFecha.obtenerFechaActual());

        cell = row.createCell(6);
        cell.setCellStyle(negStyle);
        cell.setCellValue("T.C.");

        cell = row.createCell(7);
        cell.setCellStyle(tcStyle);
        cell.setCellValue(tipoCambio.floatValue());


        row = sheet.createRow(2);

        cell = row.createCell(0);
        cell.setCellStyle(negStyle);
        cell.setCellValue("CATEGORIA");

        cell = row.createCell(1);
        cell.setCellStyle(negStyle);
        cell.setCellValue("SUB-CATEG.");

        cell = row.createCell(2);
        cell.setCellStyle(negStyle);
        cell.setCellValue("EMPRESA");

        cell = row.createCell(3);
        cell.setCellStyle(negStyle);
        cell.setCellValue("SEDE");

        cell = row.createCell(4);
        cell.setCellStyle(negStyle);
        cell.setCellValue("ARTICULO");

        cell = row.createCell(5);
        cell.setCellStyle(negStyle);
        cell.setCellValue("PARTIDA/LOTE");

        cell = row.createCell(6);
        cell.setCellStyle(negStyle);
        cell.setCellValue("UM");

        cell = row.createCell(7);
        cell.setCellStyle(negStyle);
        cell.setCellValue("CANTIDAD");

        cell = row.createCell(8);
        cell.setCellStyle(negStyle);
        cell.setCellValue("VALOR $");

        cell = row.createCell(9);
        cell.setCellStyle(negStyle);
        cell.setCellValue("VALOR S/.");


        int countRow = 3;

        BigDecimal costoTotal = BigDecimal.ZERO;

        for (CategoriaArticulo categoria : bk.getListaCategoriasOrdenada()) {

            ArticuloSede articuloSede = new ArticuloSede();
            articuloSede.setEmpresa(session.getEmpresa());
            articuloSede.setArticulo(new Articulo());
            articuloSede.getArticulo().setIdCategoriaArticulo(categoria);

            List<ArticuloSede> listaValores = null;
            try {
                listaValores = (List<ArticuloSede>) servicio.listaArticulosParaReporte(articuloSede);
            } catch (ServiceException e) {
                e.printStackTrace();
            }

            if (listaValores != null) {


                String nomCat = categoria.getNombre();
                Sede sedeAnt = null;
                CategoriaArticulo catAnt = null;


                BigDecimal cantidadTotal = BigDecimal.ZERO;
                BigDecimal costoSubCat = BigDecimal.ZERO;
                BigDecimal cantidadSubCat = BigDecimal.ZERO;
                BigDecimal costoSede = BigDecimal.ZERO;
                BigDecimal cantidadSede = BigDecimal.ZERO;

                for (ArticuloSede artSede : listaValores) {
                    row = sheet.createRow(countRow);

                    if (!nomCat.equals("")) {
                        cell = row.createCell(0);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(nomCat);
                        nomCat = "";

                    }
                    System.out.println("sede 1: " + artSede.getSede());
                    System.out.println("sede 2: " + sedeAnt);
                    if (artSede.getArticulo().getIdCategoriaArticulo() != catAnt) {
                        costoSubCat = costoSubCat.add(costoSede);
                        cantidadSubCat = cantidadSubCat.add(cantidadSede);
                        if (costoSubCat != BigDecimal.ZERO) {

                            row = resultadoSede(
                                    row, resStyle, cantidadSede, costoSede, costoSede.multiply(tipoCambio));
                            countRow = countRow + 2;
                            row = sheet.createRow(countRow);

                            row = resultadoCategoria(
                                    row, resCStyle, cantidadSubCat, costoSubCat, costoSubCat.multiply(tipoCambio), catAnt.getNombre());
                            countRow = countRow + 2;
                            row = sheet.createRow(countRow);
                        }


                        cell = row.createCell(1);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(artSede.getArticulo().getIdCategoriaArticulo().getNombre());

                        cell = row.createCell(2);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(buscarRazonSocial(artSede.getSede()));

                        cell = row.createCell(3);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(artSede.getSede().getNombre());

                        costoTotal = costoTotal.add(costoSubCat);

                        costoSede = BigDecimal.ZERO;
                        cantidadSede = BigDecimal.ZERO;
                        costoSubCat = BigDecimal.ZERO;
                        cantidadSubCat = BigDecimal.ZERO;


                        catAnt = artSede.getArticulo().getIdCategoriaArticulo();

                    } else if (artSede.getSede() != sedeAnt) {
                        System.out.println("sede 3: " + artSede.getSede());
                        System.out.println("sede 4: " + sedeAnt);
                        sedeAnt = artSede.getSede();
                        if (costoSede.doubleValue() != 0) {

                            row = resultadoSede(row, resStyle, cantidadSede, costoSede, costoSede.multiply(tipoCambio));
                            countRow = countRow + 2;
                            row = sheet.createRow(countRow);

                        }
                        cell = row.createCell(2);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(buscarRazonSocial(artSede.getSede()));

                        cell = row.createCell(3);
                        cell.setCellStyle(titStyle);
                        cell.setCellValue(artSede.getSede().getDireccion());

                        costoSubCat = costoSubCat.add(costoSede);
                        cantidadSubCat = cantidadSubCat.add(cantidadSede);

                        costoSede = BigDecimal.ZERO;
                        cantidadSede = BigDecimal.ZERO;

                    }
                    cell = row.createCell(4);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(artSede.getArticulo().getNombreComercial());

                    cell = row.createCell(5);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(artSede.getId().getPartidaLote());

                    cell = row.createCell(6);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(artSede.getUnidadMedida().getAbrev());

                    BigDecimal valorTotal = artSede.getCaStockDisponible().multiply(artSede.getVaCosto());

                    norStyle.setDataFormat(HSSFDataFormat.getBuiltinFormat("0.00"));
                    cell = row.createCell(7);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(artSede.getCaStockDisponible().doubleValue());

                    cell = row.createCell(8);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(valorTotal.doubleValue());

                    cell = row.createCell(9);
                    cell.setCellStyle(norStyle);
                    cell.setCellValue(valorTotal.multiply(tipoCambio).doubleValue());

                    costoSede = costoSede.add(valorTotal);

                    cantidadSede = cantidadSede.add(artSede.getCaStockDisponible());

                    countRow++;

                }

                if (catAnt != null) {

                    costoSubCat = costoSubCat.add(costoSede);
                    cantidadSubCat = cantidadSubCat.add(cantidadSede);
                    costoTotal = costoTotal.add(costoSubCat);
                    row = sheet.createRow(countRow);


                    row = resultadoSede(
                            row, resStyle, cantidadSede, costoSede, costoSede.multiply(tipoCambio));
                    countRow = countRow + 2;



                    row = sheet.createRow(countRow);

                    row = resultadoCategoria(
                            row, resCStyle, cantidadSubCat, costoSubCat, costoSubCat.multiply(tipoCambio), catAnt.getNombre());
                    countRow = countRow + 2;
                }

            }


        }
        countRow = countRow + 2;
        row = sheet.createRow(countRow);
        resStyle.setDataFormat(HSSFDataFormat.getBuiltinFormat("0.00"));
        cell = row.createCell(8);
        cell.setCellStyle(resStyle);
        cell.setCellValue(costoTotal.doubleValue());

        cell = row.createCell(9);
        cell.setCellStyle(resStyle);
        cell.setCellValue(costoTotal.multiply(tipoCambio).doubleValue());

        SimpleDateFormat sdf = new SimpleDateFormat(Constantes.Fecha.FORMATO_FECHA_ARCHIVO);
        String hoy = sdf.format(fecha);
        String filename = "Inventario_" + hoy + ".xls";
        FacesContext facesContext = FacesContext.getCurrentInstance();
        ExternalContext externalContext = facesContext.getExternalContext();

        externalContext.setResponseContentType("application/vnd.ms-excel");
        externalContext.setResponseHeader("Content-Disposition", "attachment; filename=" + filename);


        try {
            if (bk.isCerrar()) {
                FileOutputStream out = new FileOutputStream("C:\\" + filename);
                wb.write(out);
            }

            wb.write(externalContext.getResponseOutputStream());
            facesContext.responseComplete();
        } catch (IOException e) {
            e.printStackTrace();
        }

        try {
            if (bk.isCerrar()) {
                CierreInventario cierre = new CierreInventario();

                cierre.setFecCreacion(fecha);
                cierre.setUsrCreacion(session.getUsuario().getUsuario());
                cierre.setArchivo(filename);
                cierre.setIdEmpresa(session.getEmpresa());
                servicioCierreInventario.guardarCierreInventario(cierre);
            }
        } catch (ServiceException e) {
            e.printStackTrace();
        }

    }

    public HSSFRow resultadoSede(HSSFRow row, HSSFCellStyle resStyle, BigDecimal cantidad, BigDecimal totalDolares, BigDecimal totalSoles) {
        HSSFCell cell;

        cell = row.createCell(3);
        cell.setCellStyle(resStyle);
        cell.setCellValue("Total Sede: ");

        cell = row.createCell(4);
        cell.setCellStyle(resStyle);

        cell = row.createCell(5);
        cell.setCellStyle(resStyle);

        cell = row.createCell(6);
        cell.setCellStyle(resStyle);

        resStyle.setDataFormat(HSSFDataFormat.getBuiltinFormat("0.00"));
        cell = row.createCell(7);
        cell.setCellStyle(resStyle);
        cell.setCellValue(cantidad.doubleValue());

        cell = row.createCell(8);
        cell.setCellStyle(resStyle);
        cell.setCellValue(totalDolares.doubleValue());

        cell = row.createCell(9);
        cell.setCellStyle(resStyle);
        cell.setCellValue(totalSoles.doubleValue());

        return row;

    }

    public HSSFRow resultadoCategoria(HSSFRow row, HSSFCellStyle resCStyle, BigDecimal cantidad, BigDecimal totalDolares, BigDecimal totalSoles, String nomCat) {
        HSSFCell cell;
        cell = row.createCell(1);
        cell.setCellStyle(resCStyle);
        cell.setCellValue("Total " + nomCat + " :");

        cell = row.createCell(2);
        cell.setCellStyle(resCStyle);

        cell = row.createCell(3);
        cell.setCellStyle(resCStyle);

        cell = row.createCell(4);
        cell.setCellStyle(resCStyle);

        cell = row.createCell(5);
        cell.setCellStyle(resCStyle);

        cell = row.createCell(6);
        cell.setCellStyle(resCStyle);

        resCStyle.setDataFormat(HSSFDataFormat.getBuiltinFormat("0.00"));
        cell = row.createCell(7);
        cell.setCellStyle(resCStyle);
        cell.setCellValue(cantidad.doubleValue());

        cell = row.createCell(8);
        cell.setCellStyle(resCStyle);
        cell.setCellValue(totalDolares.doubleValue());

        cell = row.createCell(9);
        cell.setCellStyle(resCStyle);
        cell.setCellValue(totalSoles.doubleValue());

        return row;

    }
}
